package com.houserent.service;

import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.text.NumberFormat;
import java.util.Calendar;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;

import com.houserent.dao.AcctDao;
import com.houserent.dao.HouseDao;
import com.houserent.dao.LogDao;
import com.houserent.dao.MsgDao;
import com.houserent.dao.OrderDao;
import com.houserent.entry.HouseInfo;
import com.houserent.entry.HouseResult;
import com.houserent.entry.LogInfo;
import com.houserent.entry.MsgInfo;
import com.houserent.entry.OrderInfo;
import com.houserent.utils.HouseUtils;

@Service
@Transactional
public class HouseServiceImpl implements HouseService {

    @Resource
    private HouseDao houseDao;
    @Resource
    private OrderDao orderDao;
    @Resource
    private MsgDao msgDao;
    @Resource
    private LogDao logDao;
    @Resource
    private AcctDao acctDao;

    // allInfoTag=1时,返回房屋使用信息,订单信息,消息信息
    @Override
    public HouseResult getHouseUseInfo(String userId, String allInfoTag) {
        Map retMap = new HashMap();// 最终返回的map
        List<String> canUseTagList = houseDao.getHouseUseInfo(userId);
        // 1.计算房子的使用数,未使用数,总数和使用率
        int inUse = 0;
        int empty = 0;
        int nearEndHouse = 0;
        if (!HouseUtils.isEmpty(canUseTagList)) {
            for (String tag : canUseTagList) {
                if ("1".equals(tag)) {// 可以使用
                    empty++;
                }
                else if ("0".equals(tag)) {// 已经有人入住
                    inUse++;
                }
            }

            // 用户有房子的情况下再计算即将到期房子的数量
            List<Map> orders = orderDao.getBeUseHouse(userId);
            if (!HouseUtils.isEmpty(orders)) {
                for (Map order : orders) {
                    String exceptEndDate = (String) order.get("expect_end_date");
                    if (3 != (Integer) order.get("order_status")) {// 进行中订单
                        int endDate = HouseUtils.daysOfTwo(exceptEndDate, HouseUtils.getSysDate(), "yyyyMMddHHmmss");
                        if (0 <= endDate && endDate <= 5) { // 即将到期
                            nearEndHouse++;
                        }
                        // 计算出下次缴费时间
                        String lastFeeTime = (String) order.get("last_fee_time");
                        String nextFeeTime = HouseUtils.rollDateStr(lastFeeTime, "yyyyMMddHHmmss", Calendar.MONTH, 1);
                        order.put("nextFeeTime", HouseUtils.TransDate(nextFeeTime, "yyyyMMddHHmmss", "yyyy-MM-dd"));
                    }
                    // 转换日期格式
                    order.put("expect_end_date", HouseUtils.TransDate(exceptEndDate, "yyyyMMddHHmmss", "yyyy-MM-dd"));
                }
                if ("1".equals(allInfoTag)) {// 获取全部信息的标记1-获取全部信息,0-获取使用信息
                    retMap.put("orderInfo", orders);
                }
            }
        }

        int houseCount = canUseTagList.size();
        Map dataMap = HouseUtils.asMap("inUse", inUse, "empty", empty, "houseCount", houseCount);
        String houseUseRatio = "0%";
        if (houseCount != 0) {// 计算房屋使用率
            NumberFormat numberFormat = NumberFormat.getInstance();
            numberFormat.setMaximumFractionDigits(1);
            houseUseRatio = numberFormat.format((float) inUse / (float) houseCount * 100) + "%";
        }
        dataMap.put("ratio", houseUseRatio);
        dataMap.put("nearEndHouse", nearEndHouse);

        retMap.put("useInfo", dataMap);// 房屋使用信息
        if ("1".equals(allInfoTag)) {// 获取消息
            LogInfo user = logDao.login(userId);
            Map sqlMap = HouseUtils.asMap("userId", userId);
            if ("01".equals(user.getUser_type())) {// 如果是房客
                HouseInfo house = houseDao.getHouseInfoByHouseUser(userId);
                sqlMap.put("hostId", house.getHost_id());
            }
            else {
                sqlMap.put("hostId", userId);
            }
            List<MsgInfo> msgs = msgDao.getMsgByUserId(sqlMap);
            if (!HouseUtils.isEmpty(msgs)) {
                retMap.put("msgInfo", msgs);
            }
        }
        return new HouseResult(HouseResult.SUCCESS_CODE, "查询成功", retMap);
    }

    @Override
    public HouseResult addHousePic(MultipartFile roompic, HttpServletRequest request, HttpServletResponse response)
            throws IOException {
        request.setCharacterEncoding("UTF-8");
        response.setContentType("text/html;charset=UTF-8");
        byte[] logoBytes = null;
        if (!roompic.isEmpty()) {
            try {
                logoBytes = roompic.getBytes();
                BufferedOutputStream stream = new BufferedOutputStream(new FileOutputStream(new File("roompic")));
                stream.write(logoBytes);
                stream.close();
            }
            catch (Exception e) {
                return new HouseResult(HouseResult.ERROR_CODE, "上传图片出错!请重新上传", "");
            }
        }
        else {
            return new HouseResult(HouseResult.ERROR_CODE, "上传的图片有误!请重新选择", "");
        }
        if (HouseUtils.isEmpty(logoBytes) || logoBytes.length > 16 * 1024 * 1024) {// 4M
            return new HouseResult(HouseResult.ERROR_CODE, "上传图片过大!请重新选择", "");
        }
        String houseId = HouseUtils.createHouseID();
        HouseInfo house = new HouseInfo(houseId, "", "", "", "", "", "", "", 9999, 0, 0, 0, "", "", "", "", "", "", "",
                "");
        house.setHouse_pic(logoBytes);
        house.setCan_use_tag("0");// 设置为不可用
        house.setValid_tag("0");// 设置为数据失效
        house.setUnuse_date(HouseUtils.getSysDate());// 设置失效时间
        houseDao.addHousePic(house);
        return new HouseResult(HouseResult.SUCCESS_CODE, "图片上传成功", houseId);
    }

    // 添加房间信息,单个新增,批量新增
    @Override
    public HouseResult addHouse(String houseId, String hostId, String roomNubmerType, String roomAddress,
            String roomType, String addressDetial, String roomnumber, String houseRent, String powerCharge,
            String waterCharge, String guarantyFee, String houseGoods) {
        if (HouseUtils.isEmpty(roomNubmerType)) {
            return new HouseResult(HouseResult.ERROR_CODE, "房间号类型不正确!请重新录入", "");
        }
        HouseInfo house = houseDao.getHouseInfoByHouseId(houseId);
        LogInfo host = logDao.login(hostId);
        if (HouseUtils.isEmpty(house) || HouseUtils.isEmpty(host)) {
            return new HouseResult(HouseResult.ADD_HOUSE_ERROR_CODE, "新增房间出错,请重新添加", "");
        }
        String[] roomNumbers;
        if ("2".equals(roomNubmerType)) {// 按规则生成
            try {
                roomNumbers = createRoomNumbers(roomnumber.split(","));// 共3个,房间号开始,房间数量,房间号间隔
            }
            catch (Exception e) {
                e.printStackTrace();
                return new HouseResult(HouseResult.ERROR_CODE, "生成房间号出错,请确认输入的值", "");
            }
        }
        else if ("1".equals(roomNubmerType)) {// 自定义房间号,用逗号隔开的房间号
            roomNumbers = roomnumber.split(",");
        }
        else {// 单个新增,只有一个房间号
            roomNumbers = new String[] { roomnumber };
        }
        for (String roomNumber : roomNumbers) {
            HouseInfo addHouse = new HouseInfo();
            addHouse.setHost_id(hostId);
            addHouse.setHouse_address(roomAddress);
            addHouse.setDetail_address(addressDetial);
            addHouse.setHouse_number(roomNumber);
            addHouse.setHouse_rent(Double.parseDouble(houseRent));
            addHouse.setPower_charge(Double.parseDouble(powerCharge));
            addHouse.setWater_charge(Double.parseDouble(waterCharge));
            addHouse.setGuaranty_fee(Double.parseDouble(guarantyFee));
            if (houseGoods.endsWith(",")) {
                houseGoods = houseGoods.substring(0, houseGoods.length() - 1);
            }
            addHouse.setHouse_goods(houseGoods);
            addHouse.setCan_use_tag("1");
            addHouse.setValid_tag("1");
            addHouse.setUnuse_date("");
            addHouse.setHost_phone(host.getLink_phone());
            addHouse.setJoin_date(HouseUtils.getSysDate());
            addHouse.setHouse_type(roomType);
            addHouse.setHouse_pic(house.getHouse_pic());
            if (houseId.equals(house.getHouse_id())) {// 单个新增时,更新原数据
                addHouse.setHouse_id(houseId);
                houseDao.simAdd(addHouse);
                houseId = "";
            }
            else {
                addHouse.setHouse_id(HouseUtils.createHouseID());
                houseDao.addHousePic(addHouse);
            }
        }
        return new HouseResult(HouseResult.SUCCESS_CODE, "房间添加完成!", "");
    }

    @Override
    public HouseResult qryAllHouse(String userId) {
        List<Map> houseList = houseDao.getHouseInfoByHostId(userId);
        if (HouseUtils.isEmpty(houseList)) {
            return new HouseResult(HouseResult.ERROR_CODE, "您暂未发布房间信息", "");
        }
        for (Map house : houseList) {
            byte[] housepic = (byte[]) house.get("house_pic");
            String picPath = HouseUtils.PIC_PATH + "pic" + house.get("house_id") + ".png";
            File picFile = new File(picPath);
            if (!picFile.exists()) {
                try {
                    BufferedOutputStream stream = new BufferedOutputStream(new FileOutputStream(new File(picPath)));
                    stream.write(housepic);
                    stream.close();
                }
                catch (Exception e) {
                    e.printStackTrace();
                    return new HouseResult(HouseResult.ERROR_CODE, "图片加载失败!", "");
                }
            }
            house.put("house_pic", picPath.substring(picPath.indexOf("/housePic") + 1));
        }
        return new HouseResult(HouseResult.SUCCESS_CODE, "查询成功", houseList);
    }

    /**
     * 按规则生成房间号
     * @param roles
     * @return
     */
    private static String[] createRoomNumbers(String[] roles) {
        int numberStart = Integer.valueOf(roles[0]);
        int roomCount = Integer.valueOf(roles[1]);
        int space = Integer.valueOf(roles[2]);
        String[] roomNumbers = new String[roomCount];
        for (int i = 0; i < roomCount; i++) {
            roomNumbers[i] = i * space + numberStart + "";
        }
        return roomNumbers;
    }

    @Override
    public HouseResult getUserInfo(String userId) {
        // 获取房客的信息
        Map retMap = new HashMap();
        OrderInfo order = orderDao.selOdrerInfoByUserId(userId);
        if (HouseUtils.isEmpty(order)) {
            return new HouseResult(HouseResult.ERROR_CODE, "未获取到用户的订单信息", "");
        }
        // 到期时间和押金
        Map useInfo = HouseUtils.asMap("endDate", order.getExpect_end_date(), "guarantyFee", order.getPara1());
        useInfo.put("hostId", order.getHost_id());
        // 2.获取消息
        Map sqlMap = HouseUtils.asMap("userId", userId);
        HouseInfo house = houseDao.getHouseInfoByHouseUser(userId);
        sqlMap.put("hostId", house.getHost_id());
        List<MsgInfo> msgs = msgDao.getMsgByUserId(sqlMap);
        // 3.获取账单信息
        List<Map> accts = acctDao.getAcctInfoByUserId(userId);
        useInfo.put("houseId", house.getHouse_id());
        useInfo.put("hostId", house.getHost_id());
        retMap.put("useInfo", useInfo);
        retMap.put("msgInfo", msgs);
        retMap.put("acctInfo", accts);
        return new HouseResult(HouseResult.SUCCESS_CODE, "查询成功", retMap);
    }
}
